package com.taxshare.api.service;


import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.codec.Base64;
import cn.hutool.http.HttpUtil;
import cn.hutool.json.JSONUtil;
import com.taxshare.api.constant.ResultConstant;
import com.taxshare.api.util.SignStringUtil;
import com.taxshare.api.view.vo.PurchaserApiRespVO;
import com.taxshare.response.beans.Response;
import com.taxshare.api.view.dto.*;

import com.taxshare.tools.constant.CommonConstant;
import com.taxshare.tools.util.Base64Util;
import com.taxshare.tools.util.SignUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Service;
import org.springframework.web.client.RestTemplate;

import java.util.HashMap;
import java.util.List;
import java.util.Map;


/**
 * @author lzy
 * @title: PurcharseInvoiceAuthService
 * @projectName pingan
 * @description:
 * @date 2021-03-18 21:55
 */
@Service
@Slf4j
public class InvoiceAuthService {

    @Value("${purchaser.appid}")
    private String appid;

    @Value("${purchaser.appsecret}")
    private String appsecret;

    @Value("${purchaser.jtnsrsbh}")
    private String jtnsrsbh;

    @Value("${purchaser.url}")
    private String url;

    @Value("${purchaser.zptb}")
    private String zptb;

    @Value("${purchaser.skssq}")
    private String skssq;

    @Value("${purchaser.fprzsq}")
    private String fprzsq;

    @Value("${purchaser.fprzsqjg}")
    private String fprzsqjg;

    @Value("${purchaser.fprzsqqr}")
    private String fprzsqqr;

    @Value("${purchaser.fprzsqqrjg}")
    private String fprzsqqrjg;

    @Value("${purchaser.fprzNew}")
    private String fprzNew;

    @Autowired
    RestTemplate customRest;

    /**
     * 发票认证
     *
     * @param bean
     * @return
     */
    public Response auth(InvoiceAuthBodyDTO bean) {
        List fpList = bean.getFpList();
        if (null == fpList || fpList.size() == 0) {
            return Response.error(ResultConstant.RET_API0001_CODE, ResultConstant.RET_API0001_MSG);
        } else if (fpList.size() > 100) {
            log.error("传入发票长度：", fpList.size());
            return Response.error(ResultConstant.RET_API0002_CODE, ResultConstant.RET_API0002_MSG);
        }
        Map<String, Object> contentMap = new HashMap<>(8);
        contentMap.put("Period", bean.getPeriod());
        contentMap.put("InvoiceList", fpList);
        contentMap.put("DeductibleMode",bean.getAuthMode());
        PurchaserApiDTO purchaserApiDTO = new PurchaserApiDTO();
        purchaserApiDTO.setAppid(appid);
        purchaserApiDTO.setJtnsrsbh(jtnsrsbh);
        purchaserApiDTO.setServiceid(fprzNew);
        purchaserApiDTO.setNsrsbh(bean.getNsrsbh());
        purchaserApiDTO.setContent(Base64.encode(JSONUtil.toJsonStr(contentMap)));
        purchaserApiDTO.setSignature(SignStringUtil.sign(appsecret, purchaserApiDTO.toString()));
        return dealPost(purchaserApiDTO);
    }


    /**
     * 发票认证申请
     *
     * @param bean
     * @return
     */
    public Response apply(ApplyDTO bean) {
        PurchaserApiDTO purchaserApiDTO = new PurchaserApiDTO();
        purchaserApiDTO.setAppid(appid);
        purchaserApiDTO.setJtnsrsbh(jtnsrsbh);
        purchaserApiDTO.setServiceid(fprzsq);
        purchaserApiDTO.setNsrsbh(bean.getNsrsbh());
        purchaserApiDTO.setContent(Base64.encode(JSONUtil.toJsonStr(bean)));
        purchaserApiDTO.setSignature(SignStringUtil.sign(appsecret, purchaserApiDTO.toString()));
        return dealPost(purchaserApiDTO);
    }

    /**
     * 发票认证申请结果
     *
     * @param bean
     * @return
     */
    public Response applyResult(ApplyResultDTO bean) {
        PurchaserApiDTO purchaserApiDTO = new PurchaserApiDTO();
        purchaserApiDTO.setAppid(appid);
        purchaserApiDTO.setJtnsrsbh(jtnsrsbh);
        purchaserApiDTO.setServiceid(fprzsqjg);
        purchaserApiDTO.setNsrsbh(bean.getNsrsbh());
        purchaserApiDTO.setContent(Base64.encode(JSONUtil.toJsonStr(bean)));
        purchaserApiDTO.setSignature(SignStringUtil.sign(appsecret, purchaserApiDTO.toString()));
        return dealPost(purchaserApiDTO);
    }

    /**
     * 发票认证申请确认签名
     *
     * @param bean
     * @return
     */
    public Response confirm(ConfirmApplyDTO bean) {
        PurchaserApiDTO purchaserApiDTO = new PurchaserApiDTO();
        purchaserApiDTO.setAppid(appid);
        purchaserApiDTO.setJtnsrsbh(jtnsrsbh);
        purchaserApiDTO.setServiceid(fprzsqqr);
        purchaserApiDTO.setNsrsbh(bean.getNsrsbh());
        purchaserApiDTO.setContent(Base64.encode(JSONUtil.toJsonStr(bean)));
        purchaserApiDTO.setSignature(SignStringUtil.sign(appsecret, purchaserApiDTO.toString()));
        return dealPost(purchaserApiDTO);
    }

    /**
     * 发票认证申请确认签名结果
     *
     * @param bean
     * @return
     */
    public Response confirmResult(ConfirmApplyResultDTO bean) {
        PurchaserApiDTO purchaserApiDTO = new PurchaserApiDTO();
        purchaserApiDTO.setAppid(appid);
        purchaserApiDTO.setJtnsrsbh(jtnsrsbh);
        purchaserApiDTO.setServiceid(fprzsqqrjg);
        purchaserApiDTO.setNsrsbh(bean.getNsrsbh());
        purchaserApiDTO.setContent(Base64.encode(JSONUtil.toJsonStr(bean)));
        purchaserApiDTO.setSignature(SignStringUtil.sign(appsecret, purchaserApiDTO.toString()));
        return dealPost(purchaserApiDTO);
    }

    /**
     * 获取纳税人所属期
     * @param nsrsbh
     * @return
     */
    public Response period(String nsrsbh) {
        PurchaserApiDTO purchaserApiDTO = new PurchaserApiDTO();
        purchaserApiDTO.setAppid(appid);
        purchaserApiDTO.setJtnsrsbh(jtnsrsbh);
        purchaserApiDTO.setServiceid(skssq);
        purchaserApiDTO.setNsrsbh(nsrsbh);
        purchaserApiDTO.setContent("");
        purchaserApiDTO.setSignature(SignStringUtil.sign(appsecret, purchaserApiDTO.toString()));
        return dealPost(purchaserApiDTO);
    }

    /**
     * 电子底账同步
     *
     * @param bean
     */
    public Response sync(InvoiceSyncDTO bean) {
        PurchaserApiDTO purchaserApiDTO = new PurchaserApiDTO();
        purchaserApiDTO.setAppid(appid);
        purchaserApiDTO.setJtnsrsbh(jtnsrsbh);
        purchaserApiDTO.setServiceid(zptb);
        purchaserApiDTO.setNsrsbh(bean.getNsrsbh());
        purchaserApiDTO.setContent(Base64.encode(JSONUtil.toJsonStr(bean)));
        purchaserApiDTO.setSignature(SignStringUtil.sign(appsecret, purchaserApiDTO.toString()));
        return dealPost(purchaserApiDTO);
    }


    /**
     * 统一接口调用
     * @param purchaserApiDTO
     * @return
     * @throws Exception
     */
    private Response dealPost(PurchaserApiDTO purchaserApiDTO) {
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_JSON);
        HttpEntity request = new HttpEntity<>(purchaserApiDTO, headers);
        ResponseEntity<PurchaserApiRespVO> response = customRest.postForEntity(url, request, PurchaserApiRespVO.class);
        PurchaserApiRespVO resVO = response.getBody();
        //获取返回报文失败编码和消息并返回
        if (!CommonConstant.INTERFACE_SUCCESS.equals(resVO.getCode())) {
            return Response.error(resVO.getCode(), resVO.getMsg(), Base64Util.decode(resVO.getContent()));
        } else {
            return Response.success(Base64Util.decode(resVO.getContent()));
        }
    }
}
